home *** CD-ROM | disk | FTP | other *** search
/ InfoMagic Internet Tools 1993 July / Internet Tools.iso / RockRidge / ip / manage / snmp / mit / snmpnext / snmpnext.c < prev    next >
Encoding:
C/C++ Source or Header  |  1991-05-17  |  9.6 KB  |  449 lines

  1.  
  2. /*
  3.  *    $Header: snmpnext.c,v 3.0 91/05/17 16:14:59 jrd Rel $
  4.  *    Author: J. Davin
  5.  *    Copyright 1988, 1989, Massachusetts Institute of Technology
  6.  *    See permission and disclaimer notice in file "notice.h"
  7.  */
  8.  
  9. #include    <notice.h>
  10.  
  11. #include        <sys/types.h>
  12. #include        <sys/socket.h>
  13. #include        <netinet/in.h>
  14. #include        <stdio.h>
  15. #include        <netdb.h>
  16. #include        <signal.h>
  17.  
  18. #include    <host.h>
  19.  
  20. #include    <ctypes.h>
  21. #include    <local.h>
  22. #include    <rdx.h>
  23. #include    <debug.h>
  24. #include    <smp.h>
  25. #include    <aps.h>
  26. #include    <ap0.h>
  27. #include    <asn.h>
  28. #include    <smx.h>
  29. #include    <udp.h>
  30.  
  31. #define        cmdBufferSize        (2048)
  32. #define        cmdBindListSize        (20)
  33. #define        cmdTextSize        (128)
  34.  
  35. static    void    cmdInit ()
  36.  
  37. {
  38.     aslInit ();
  39.     asnInit ();
  40.     apsInit ();
  41.     ap0Init ();
  42.     smpInit ();
  43. }
  44.  
  45. static        CBoolType        cmdDone;
  46. static        CByteType        buf [ cmdBufferSize ];
  47. static        SmpBindType        bindList [ cmdBindListSize ];
  48. static        SmpRequestType        req;
  49. static        SmpSequenceType        requestId;
  50.  
  51. static  SmpStatusType   myUpCall (smp, req)
  52.  
  53. SmpIdType               smp;
  54. SmpRequestPtrType       req;
  55.  
  56. {
  57.     int            cmp;
  58.     SmpIndexType        i;
  59.     SmpBindPtrType        bind;
  60.     SmpBindPtrType        orig;
  61.     CCharType        text [ (cmdTextSize + 1) ];
  62.  
  63.     if ((req->smpRequestCmd != smpCommandRsp) ||
  64.         (req->smpRequestId != requestId)) {
  65.         return (errOk);
  66.     }
  67.  
  68.         smp = smp;
  69.     printf ("Request Id: %d\n", req->smpRequestId);
  70.     printf ("Error: %s\n", smxErrorToText (req->smpRequestError));
  71.     printf ("Index: %d\n", req->smpRequestIndex);
  72.     printf ("Count: %d\n", req->smpRequestCount);
  73.     printf ("\n");
  74.  
  75.     bind = req->smpRequestBinds;
  76.     for (i = req->smpRequestCount; i != 0; i--) {
  77.         if (smxNameToText (text, (CIntfType) cmdTextSize,
  78.             (CBytePtrType) bind->smpBindName,
  79.             (CIntfType) bind->smpBindNameLen) >=
  80.             (CIntfType) 0) {
  81.             printf ("Name: %s\n", text);
  82.         }
  83.         printf ("Kind: %s\n", smxKindToText (bind->smpBindKind));
  84.         if (smxValueToText (text, (CIntfType) cmdTextSize,
  85.             bind) >= (CIntfType) 0) {
  86.             printf ("Value: %s\n", text);
  87.         }
  88.         else {
  89.             printf ("Value: GARBLED\n");
  90.         }
  91.         printf ("\n");
  92.         bind++;
  93.     }
  94.  
  95.     if (req->smpRequestError == smpErrorNone) {
  96.         orig = bindList;
  97.         bind = req->smpRequestBinds;
  98.         cmp = 0;
  99.         for (i = req->smpRequestCount; (i != 0) &&
  100.             ((cmp = bcmp ((char *) bind->smpBindName,
  101.             (char *) orig->smpBindName,
  102.             (int) orig->smpBindNameLen)) == 0); i--) {
  103.             orig++;
  104.             bind++;
  105.         }
  106.         if (cmp == 0) {
  107.             req->smpRequestCmd = smpCommandNext;
  108.             req->smpRequestId = ++requestId;
  109.             (void) smpRequest (smp, req);
  110.         }
  111.         else {
  112.             cmdDone = TRUE;
  113.         }
  114.     }
  115.     else {
  116.         cmdDone = TRUE;
  117.     }
  118.         return (errOk);
  119. }
  120.  
  121. static    CIntfType    usage (s)
  122.  
  123. CCharPtrType        s;
  124.  
  125. {
  126.     fprintf (stderr, "Usage: %s", s);
  127.     fprintf (stderr, " [-h fhost]");
  128.     fprintf (stderr, " [-p fport]");
  129.     fprintf (stderr, " [-t timeout]");
  130.     fprintf (stderr, " [-i requestId]");
  131.     fprintf (stderr, " [-c community]");
  132.     fprintf (stderr, " [name] ...\n");
  133.     return (1);
  134. }
  135.  
  136. static    int        alarmHandler (sig, code, scp)
  137.  
  138. int            sig;
  139. int            code;
  140. struct    sigcontext    *scp;
  141.  
  142. {
  143.     sig = sig;
  144.     code = code;
  145.     scp = scp;
  146.     fprintf (stderr, "Request Timed Out\n");
  147.     (void) fflush (stderr);
  148.     exit (4);
  149. }
  150.  
  151. int        nxtCommand (argc, argv)
  152.  
  153. int        argc;
  154. char        **argv;
  155.  
  156. {
  157.     int            s;
  158.     int            salen;
  159.     int            result;
  160.     struct    sockaddr    salocal;
  161.     struct    sockaddr    saremote;
  162.     struct    sockaddr_in    *sin;
  163.         struct  servent         *svp;
  164.     unsigned        timeout;
  165.     struct    sigvec        newSignalVector;
  166.  
  167.     u_long            fhost;
  168.     u_short            fport;
  169.     CUnslType        number;
  170.  
  171.     CByteType        pkt [ cmdBufferSize ];
  172.     CBytePtrType        bp;
  173.     SmpIndexType        bindCount;
  174.     SmpIdType        smp;
  175.     ApsIdType        communityId;
  176.     SmpSocketType        udp;
  177.     SmpBindPtrType        bindp;
  178.     CCharPtrType        *ap;
  179.     CCharPtrType        cp;
  180.     CBoolType        noerror;
  181.     CIntfType        len;
  182.     CIntfType        space;
  183.  
  184.     CCharPtrType        communityString;
  185.     CCharPtrType        fhostString;
  186.     CCharPtrType        fportString;
  187.     CCharPtrType        requestIdString;
  188.     CCharPtrType        timeoutString;
  189.  
  190.     communityString = (CCharPtrType) 0;
  191.     fhostString = (CCharPtrType) 0;
  192.     fportString = (CCharPtrType) 0;
  193.     requestIdString = (CCharPtrType) 0;
  194.     timeoutString = (CCharPtrType) 0;
  195.  
  196.     ap = (CCharPtrType *) argv + 1;
  197.     argc--;
  198.     noerror = TRUE;
  199.     while ((argc != 0) && (**ap == (CCharType) '-') && (noerror)) {
  200.         cp = *ap;
  201.         cp++;
  202.         ap++;
  203.         argc--;
  204.         while ((*cp != (CCharType) 0) && (noerror)) {
  205.             switch (*cp) {
  206.  
  207.             case 'c':
  208.                 argc--;
  209.                 communityString = *ap++;
  210.                 break;
  211.  
  212.             case 'h':
  213.                 argc--;
  214.                 fhostString = *ap++;
  215.                 break;
  216.  
  217.             case 'i':
  218.                 argc--;
  219.                 requestIdString = *ap++;
  220.                 break;
  221.  
  222.             case 'p':
  223.                 argc--;
  224.                 fportString = *ap++;
  225.                 break;
  226.  
  227.             case 't':
  228.                 argc--;
  229.                 timeoutString = *ap++;
  230.                 break;
  231.  
  232.             default:
  233.                 noerror = FALSE;
  234.                 break;
  235.             }
  236.             cp++;
  237.         }
  238.     }
  239.  
  240.     if ((! noerror) || (fhostString == (CCharPtrType) 0)) {
  241.         return ((int) usage ((CCharPtrType) argv [ 0 ]));
  242.     }
  243.  
  244.     if (argc > cmdBindListSize) {
  245.         return ((int) usage ((CCharPtrType) argv [ 0 ]));
  246.     }
  247.  
  248.     fhost = (u_long) hostAddress (fhostString);
  249.     if (fhost == (u_long) -1) {
  250.         fprintf (stderr, "%s: Bad foreign host: %s\n",
  251.             argv [ 0 ], fhostString);
  252.         return (2);
  253.     }
  254.  
  255.     if (fportString != (CCharPtrType) 0) {
  256.                 if (rdxDecodeAny (& number, fportString) < (CIntfType) 0) {
  257.                         fprintf (stderr, "%s: Bad local port: %s\n",
  258.                                 argv [ 0 ], fportString);
  259.                         return (2);
  260.                 }
  261.                 else {
  262.                         fport = htons ((u_short) number);
  263.                 }
  264.         }
  265.         else {
  266.                 svp = getservbyname ("snmp", "udp");
  267.                 if (svp == (struct servent *) 0) {
  268.                         fprintf (stderr, "%s: No such service: %s/%s\n",
  269.                                 argv [ 0 ], "snmp", "udp");
  270.                         return (2);
  271.                 }
  272.                 fport = (u_short) svp->s_port;
  273.         }
  274.  
  275.     if (timeoutString != (CCharPtrType) 0) {
  276.                 if (rdxDecodeAny (& number, timeoutString) < (CIntfType) 0) {
  277.                         fprintf (stderr, "%s: Bad timeout value: %s\n",
  278.                                 argv [ 0 ], timeoutString);
  279.                         return (2);
  280.                 }
  281.         else {
  282.             timeout = (unsigned) number;
  283.         }
  284.     }
  285.     else {
  286.             timeout = (unsigned) 0;
  287.     }
  288.  
  289.     if (requestIdString != (CCharPtrType) 0) {
  290.                 if (rdxDecodeAny (& number, requestIdString) < (CIntfType) 0) {
  291.                         fprintf (stderr, "%s: Bad requestId value: %s\n",
  292.                                 argv [ 0 ], requestIdString);
  293.                         return (2);
  294.                 }
  295.         else {
  296.             requestId = (SmpSequenceType) number;
  297.         }
  298.     }
  299.     else {
  300.             requestId = (SmpSequenceType) 0;
  301.     }
  302.  
  303.     if (communityString == (CCharPtrType) 0) {
  304.         communityString = (CCharPtrType) "public";
  305.     }
  306.  
  307.     cmdInit ();
  308.  
  309.     bp = buf;
  310.     space = cmdBufferSize;
  311.     bindp = bindList;
  312.     bindCount = (SmpIndexType) 0;
  313.  
  314.     for (noerror = TRUE; (noerror) && (argc > 0); argc--) {
  315.         if ((len = smxTextToObjectId (bp, space, *ap)) <
  316.             (CIntfType) 0) {
  317.             noerror = FALSE;
  318.         }
  319.         else {
  320.             ap++;
  321.             bindp->smpBindName = (SmpNameType) bp;
  322.             bindp->smpBindNameLen = (SmpLengthType) len;
  323.             bp += len;
  324.             space -= len;
  325.             bindp->smpBindKind = smpKindOctetString;
  326.             bindp->smpBindValue = (SmpValueType) 0;
  327.             bindp->smpBindValueLen = (SmpLengthType) 0;
  328.             bindp++;
  329.             bindCount++;
  330.         }
  331.     }
  332.  
  333.     if (! noerror) {
  334.         fprintf (stderr, "%s: Error parsing argument %s\n",
  335.             argv [ 0 ], *ap);
  336.         return (2);
  337.     }
  338.  
  339.     s = socket (AF_INET, SOCK_DGRAM, 0);
  340.     if (s < 0) {
  341.         (void) perror ("socket");
  342.         return (1);
  343.     }
  344.  
  345.     sin = (struct sockaddr_in *) & salocal;
  346.         bzero ((char *) sin, sizeof (*sin));
  347.     sin->sin_family = AF_INET;
  348.     sin->sin_addr.s_addr = (u_long) 0;
  349.     sin->sin_port = (u_short) 0;
  350.  
  351.     result = bind (s, & salocal, sizeof (*sin));
  352.     if (result < 0) {
  353.         (void) perror ("bind");
  354.         return (1);
  355.     }
  356.  
  357.         udp = udpNew (s, fhost, fport);
  358.         smp = smpNew (udp, udpSend, myUpCall);
  359.     if (smp == (SmpIdType) 0) {
  360.         fprintf (stderr,
  361.             "%s: Error creating protocol object\n", argv [ 0 ]);
  362.         udp = udpFree (udp);
  363.         return (2);
  364.     }
  365.  
  366.     communityId = apsNew ((ApsNameType) communityString,
  367.         (ApsNameType) "trivial", (ApsGoodiesType) 0);
  368.  
  369.     req.smpRequestCmd = smpCommandNext;
  370.     req.smpRequestCommunity = communityId;
  371.     req.smpRequestId = requestId;
  372.     req.smpRequestError = smpErrorNone;
  373.     req.smpRequestIndex = (SmpIndexType) 0;
  374.     req.smpRequestCount = bindCount;
  375.     req.smpRequestBinds = bindList;
  376.  
  377.     if (smpRequest (smp, & req) != errOk) {
  378.         fprintf (stderr, "%s: Error sending protocol request\n",
  379.             argv [ 0 ]);
  380.         smp = smpFree (smp);
  381.         udp = udpFree (udp);
  382.         communityId = apsFree (communityId);
  383.         return (2);
  384.     }
  385.     smp = smpFree (smp);
  386.  
  387.     sin = (struct sockaddr_in *) & saremote;
  388.  
  389.     if (timeout != (unsigned) 0) {
  390.         newSignalVector.sv_handler = alarmHandler;
  391.         newSignalVector.sv_mask = 0;
  392.         newSignalVector.sv_flags = 0;
  393.         if (sigvec (SIGALRM, & newSignalVector,
  394.             (struct sigvec *) 0) == -1) {
  395.             perror (argv [ 0 ]);
  396.             udp = udpFree (udp);
  397.             communityId = apsFree (communityId);
  398.             return (2);
  399.         }
  400.     }
  401.  
  402.     cmdDone = FALSE;
  403.  
  404.     do {
  405.         if (timeout != (unsigned) 0) {
  406.             (void) alarm (timeout);
  407.         }
  408.  
  409.             smp = smpNew (udp, udpSend, myUpCall);
  410.         if (smp == (SmpIdType) 0) {
  411.             fprintf (stderr,
  412.                 "%s: Error creating protocol object\n",
  413.                 argv [ 0 ]);
  414.             udp = udpFree (udp);
  415.             communityId = apsFree (communityId);
  416.             return (2);
  417.         }
  418.  
  419.         salen = sizeof (saremote);
  420.         result = recvfrom (s, (char *) pkt, (int) cmdBufferSize,
  421.             (int) 0, & saremote, & salen);
  422.         DEBUGBYTES (pkt, result);
  423.         DEBUG0 ("\n");
  424.  
  425.         for (bp = pkt; ((result > 0) &&
  426.             (smpInput (smp, *bp++) == errOk));
  427.             result--);
  428.  
  429.         smp = smpFree (smp);
  430.  
  431.         DEBUG1 ("result: %d\n", result);
  432.  
  433.     } while ((result >= 0) && (! cmdDone));
  434.  
  435.     udp = udpFree (udp);
  436.     communityId = apsFree (communityId);
  437.     return (close (s));
  438. }
  439.  
  440. int    main (argc, argv)
  441.  
  442. int     argc;
  443. char    *argv [];
  444.  
  445. {
  446.         exit (nxtCommand (argc, argv));
  447. }
  448.  
  449.